home *** CD-ROM | disk | FTP | other *** search
/ Aminet 51 / Aminet 51 (2002)(GTI - Schatztruhe)[!][Oct 2002].iso / Aminet / misc / emu / x128utils.lha / Sources / SLT2DAT.C < prev   
Encoding:
C/C++ Source or Header  |  2002-08-25  |  9.6 KB  |  478 lines

  1. /******************************************/
  2. /**                                      **/
  3. /**         SLT2DAT.C DAT Splitter       **/
  4. /**                                      **/
  5. /**          (C) James McKay 1996        **/
  6. /**                                      **/
  7. /**    This software may not be used     **/
  8. /**    for commercial reasons, the code  **/
  9. /**    may not be modified or reused     **/
  10. /**    without permission.               **/
  11. /**                                      **/
  12. /******************************************/
  13.  
  14. #define SEEK_SET 0
  15. #define SEEK_CUR 1
  16. #define SEEK_END 2
  17.  
  18. #include <stdio.h>
  19. #include <stdlib.h>
  20. #include <string.h>
  21. #include <ctype.h>
  22.  
  23. /* It is essential that a word is 16 bits wide and a char is 8 bits wide */
  24.  
  25. /* A quick fix for Borland */
  26. #ifdef __BORLANDC__
  27. #define word unsigned int
  28. #else
  29. #define word unsigned short
  30. #endif
  31.  
  32. #define UC unsigned char
  33.  
  34. #define MAXPATH 300
  35.  
  36. char input_name[MAXPATH];
  37. char output_name[MAXPATH];
  38. char param4[MAXPATH];
  39.  
  40. char *ID_String="SLT";
  41. char *ID_000="\0\0\0";
  42. char *in_buffer, *out_buffer;
  43.  
  44. long DAT_length[256];
  45. long SCR_length;
  46.  
  47. FILE *input_handle;
  48.  
  49. UC acorn_form=0;
  50.  
  51. /* Set this to 1 if compiling under DOS */
  52. UC dos_form=1;
  53.  
  54. void clean_buffers(void)
  55. {
  56.     memset(in_buffer,0,0xFFFF);
  57.     memset(out_buffer,0,0xFFFF);
  58. }
  59.  
  60. void lower_it(char *stringy)
  61. {
  62.     int pos, x;
  63.  
  64.     pos=strlen(stringy);
  65.     for(x=0;x<pos;x++)
  66.     {
  67.         stringy[x]=tolower(stringy[x]);
  68.     }
  69. }
  70.  
  71. void strip_extension(char *stringy)
  72. {
  73.     int pos;
  74.  
  75.     pos=strlen(stringy);
  76.     pos--;
  77.     while((stringy[pos]!='.')&&(pos)&&
  78.     (stringy[pos]!='\\')&&(stringy[pos]!='/')) pos--;
  79.  
  80.     if(stringy[pos]=='.') stringy[pos]='\0'; /* If ext, then cut */
  81. }
  82.  
  83. int get_length_of_pre(char *stringy)
  84. {
  85. /* Assumes that extension has already been stripped and that there is no
  86.  / or \ at the end of this string */
  87.     int pos, pre_len;
  88.  
  89.     if(acorn_form) return 0;
  90.     pos=strlen(stringy);
  91.     pos--;
  92.     pre_len=0;
  93.     while((stringy[pos]!='/')&&(stringy[pos]!='\\')&&(pos>=0))
  94.     {
  95.         pre_len++;
  96.         pos--;
  97.     }
  98.     return pre_len;
  99. }
  100.  
  101. void itoa_temp(char *stringy, UC x)
  102. {
  103.     char *original_point;
  104.     UC temp;
  105.  
  106.     original_point=stringy;
  107.     temp=0;
  108.     if(x>=100)
  109.     {
  110.         temp=0;
  111.         while(x>=100)
  112.         {
  113.             x-=100;
  114.             temp++;
  115.         }
  116.         *stringy++=temp+'0';
  117.     }
  118.     if(x>=10)
  119.     {
  120.         temp=0;
  121.         while(x>=10)
  122.         {
  123.             x-=10;
  124.             temp++;
  125.         }
  126.         *stringy++=temp+'0';
  127.     }
  128.     else
  129.     {
  130.         if(temp) /* 100's but not 10's */
  131.         {
  132.             *stringy++='0';
  133.         }
  134.     }
  135.     *stringy++=x+'0';
  136.     *stringy='\0';
  137.     stringy=original_point;
  138. }
  139.  
  140. void add_level_num(char *stringy, UC number)
  141. {
  142.     char num_str[4];
  143.     int pre_len, pos;
  144.  
  145.     itoa_temp((char *)num_str,number);
  146.     pre_len=get_length_of_pre(stringy);
  147.     if((dos_form)&&((pre_len+strlen(num_str))>8))
  148.     {
  149.         /* Snippy bits for DOS */
  150.         pos=strlen(stringy);
  151.         stringy[pos-strlen(num_str)]='\0';
  152.     }
  153.     strcat(stringy,num_str);
  154. }
  155.  
  156. word decompress_DAT(word in_length)
  157. {
  158.     unsigned long in_index, out_index;
  159.     UC value, value2, poker, loopr, x;
  160.  
  161.     in_index=out_index=0;
  162.     do{
  163.         value=in_buffer[in_index++];
  164.         if(value==237) /* is ED... */
  165.         {
  166.             value2=in_buffer[in_index++];
  167.             if (value2==237) /* is ED ED code */
  168.             {
  169.                 loopr=in_buffer[in_index++];
  170.                 poker=in_buffer[in_index++];
  171.                 for(x=0;x<loopr;x++)
  172.                 {
  173.                     out_buffer[out_index++]=poker;
  174.                 }
  175.             }
  176.             else
  177.             {
  178.                 out_buffer[out_index++]=value; /* is ED ?? */
  179.                 out_buffer[out_index++]=value2;
  180.             }
  181.         }
  182.         else
  183.         {
  184.             out_buffer[out_index++]=value; /* not ED... */
  185.         }
  186.         if(out_index>65535) /* As out_buffer is 65535 */
  187.         {
  188.             printf("V2/V3 DECOMP ERROR\n");
  189.             return 0; /* fail */
  190.         }
  191.     } while (in_index<in_length);
  192.     return (word)out_index;  /* Success! */
  193. }
  194.  
  195. void write_SCR(void)
  196. {
  197.     char temp_str[MAXPATH];
  198.     word in_length, temp_word;
  199.     FILE *temp_handle;
  200.  
  201.     in_length=(word)SCR_length;
  202.     if(!in_length) return;
  203.     clean_buffers();
  204.     fread(in_buffer,1,in_length,input_handle);
  205.  
  206.     strcpy(temp_str,output_name);
  207.     strcat(temp_str,".scr");
  208.     if(!(temp_handle = fopen(temp_str,"wb")))
  209.     {
  210.         perror("Error:");
  211.         printf("Warning: Could not create %s\n",temp_str);
  212.         return;
  213.     }
  214.     temp_word=decompress_DAT(in_length);
  215.     fwrite(out_buffer,1,temp_word,temp_handle);
  216.     fclose(temp_handle);
  217. }
  218.  
  219. void write_DAT(UC level_num)
  220. {
  221.     char temp_str[MAXPATH];
  222.     word in_length, temp_word;
  223.     FILE *temp_handle;
  224.  
  225.     in_length=(word)DAT_length[level_num];
  226.     if(!in_length) return;
  227.     clean_buffers();
  228.     fread(in_buffer,1,in_length,input_handle);
  229.  
  230.     if(acorn_form)
  231.     {
  232.         strcpy(temp_str,"");
  233.     }
  234.     else
  235.     {
  236.         strcpy(temp_str,output_name);
  237.     }
  238.     add_level_num((char *)temp_str,level_num);
  239.     if(!acorn_form) strcat(temp_str,".dat");
  240.     if(!(temp_handle = fopen(temp_str,"wb")))
  241.     {
  242.         perror("Error:");
  243.         printf("Warning: Could not create %s\n",temp_str);
  244.         return;
  245.     }
  246.     temp_word=decompress_DAT(in_length);
  247.     fwrite(out_buffer,1,temp_word,temp_handle);
  248.     fclose(temp_handle);
  249. }
  250.  
  251. void process_table(long feof_marker)
  252. {
  253.     word x, data_type;
  254.  
  255.     for(x=0;x<256;x++) DAT_length[x]=0;
  256.     SCR_length=0;
  257.     while(ftell(input_handle)!=feof_marker)
  258.     {
  259.         fread(in_buffer,1,8,input_handle);
  260.         data_type=(UC)in_buffer[0]|((UC)in_buffer[1]<<8);
  261.         switch(data_type)
  262.         {
  263.             case 0 :
  264.                 return;
  265.             case 1 :
  266.                 DAT_length[in_buffer[2]]=(UC)in_buffer[7];
  267.                 DAT_length[in_buffer[2]]<<=8;
  268.                 DAT_length[in_buffer[2]]|=(UC)in_buffer[6];
  269.                 DAT_length[in_buffer[2]]<<=8;
  270.                 DAT_length[in_buffer[2]]|=(UC)in_buffer[5];
  271.                 DAT_length[in_buffer[2]]<<=8;
  272.                 DAT_length[in_buffer[2]]|=(UC)in_buffer[4];
  273.                 break;
  274.             case 3 :
  275.                 SCR_length=(UC)in_buffer[7];
  276.                 SCR_length<<=8;
  277.                 SCR_length|=(UC)in_buffer[6];
  278.                 SCR_length<<=8;
  279.                 SCR_length|=(UC)in_buffer[5];
  280.                 SCR_length<<=8;
  281.                 SCR_length|=(UC)in_buffer[4];
  282.                 break;
  283.             default:
  284.                 break; /* No others yet defined */
  285.         }
  286.     }
  287. }
  288.  
  289. long find_end_of_z80(void)
  290. {
  291.     word temp_word;
  292.     UC done;
  293.  
  294.     fread(in_buffer,1,32,input_handle);
  295.     temp_word=in_buffer[30]|(in_buffer[31]<<8);
  296.     fread(in_buffer,1,temp_word,input_handle);
  297.     /* Now at memory blocks */
  298.     done=0;
  299.     while(!done)
  300.     {
  301.         fread(in_buffer,1,3,input_handle);
  302.         temp_word=(UC)in_buffer[0]|((UC)in_buffer[1]<<8);
  303.         if((!temp_word)&&(!in_buffer[2]))
  304.         {
  305.             done=1; /* Test for ID_000 */
  306.             fseek(input_handle,-3,SEEK_CUR);
  307.         }
  308.         else
  309.         {
  310.             fseek(input_handle,temp_word,SEEK_CUR);
  311.         }
  312.     }
  313.     return ftell(input_handle);
  314. }
  315.  
  316. void process_and_copy_z80(void)
  317. {
  318.     char temp_str[MAXPATH];
  319.  
  320.     FILE *temp_handle;
  321.     long temp_long;
  322.  
  323.     strcpy(temp_str,output_name);
  324.     strcat(temp_str,".z80");
  325.  
  326.     if(!(temp_handle = fopen(temp_str,"wb")))
  327.     {
  328.         perror("Error:");
  329.         printf("Could not create output file %s\n",temp_str);
  330.         return;
  331.     }
  332.     /* Get end of Z80 file */
  333.     temp_long=find_end_of_z80();
  334.  
  335.     fseek(input_handle,temp_long,SEEK_SET); /* Check ID String */
  336.     fread(in_buffer,1,3,input_handle);
  337.     if((in_buffer[0]|in_buffer[1]|in_buffer[2]))
  338.     {
  339.         fclose(input_handle);
  340.         fclose(temp_handle);
  341.         free(in_buffer);
  342.         free(out_buffer);
  343.         printf("This is not a SLT file, ID_000 failed!\n");
  344.         exit(1);
  345.     }
  346.     fread(in_buffer,1,strlen(ID_String),input_handle);
  347.     in_buffer[strlen(ID_String)]='\0';
  348.     if(strcmp(in_buffer,ID_String))
  349.     {
  350.         fclose(input_handle);
  351.         fclose(temp_handle);
  352.         free(in_buffer);
  353.         free(out_buffer);
  354.         printf("This is not a SLT file, ID_String failed!\n");
  355.         exit(1);
  356.     }
  357.  
  358.     fseek(input_handle,0,SEEK_SET);
  359.     while(temp_long>32767)
  360.     {
  361.         fread(in_buffer,1,32768,input_handle);
  362.         fwrite(in_buffer,1,32768,temp_handle);
  363.         temp_long-=32768;
  364.     }
  365.     if(temp_long>0)
  366.     {
  367.         fread(in_buffer,1,(word)temp_long,input_handle);
  368.         fwrite(in_buffer,1,(word)temp_long,temp_handle);
  369.     }
  370.     fclose(temp_handle);
  371. }
  372.  
  373. void main(int argc, char *argv[])
  374. {
  375.     char temp_str[MAXPATH];
  376.     char temp_str2[MAXPATH];
  377.     long temp_long;
  378.     word x;
  379.  
  380.     printf("SLT2DAT DAT splitter by James McKay\n");
  381.     printf("Amiga port by Wojciech Pasiecznik/Voy/SSG/Dial (voydial@wp.pl) [250802]\n");
  382.     if(argc==1)
  383.     {
  384.         printf("\nThis utility splits the SLT into a Z80 and\n");
  385.         printf(" multiple DAT files and loading SCR.\n");
  386.         printf("\nUsage: SLT2DAT <input.slt> <output.z80> [/dos]\n");
  387.         printf("/dos forces MS-DOS style filenames.\n");
  388.         printf("/acorn makes utility look for a DAT that just has");
  389.         printf(" the number as the name.\n");
  390.         exit(1);
  391.     }
  392.     if(argc<3)
  393.     {
  394.         printf("Must have input filename and output filename\n");
  395.         exit(1);
  396.     }
  397.     strcpy(input_name,argv[1]);
  398.     strcpy(output_name,argv[2]);
  399.     strip_extension((char *)input_name);
  400.     strip_extension((char *)output_name);
  401.     if(argc==4)
  402.     {
  403.         strcpy(param4,argv[3]);
  404.         if(param4[0]=='-') param4[0]='/';
  405.         lower_it((char *)param4);
  406.         if(!strcmp("/dos",param4))
  407.         {
  408.             dos_form=1;
  409.             printf("Using 8 letter format\n");
  410.         }
  411.         else
  412.         {
  413.             if(!strcmp("/acorn",param4))
  414.             {
  415.                 acorn_form=1;
  416.                 printf("Using Acorn 'no name' format.\n");
  417.             }
  418.             else
  419.             {
  420.                 printf("Last parameter can only be /dos");
  421.                 printf(" or /acorn\n");
  422.                 exit(1);
  423.             }
  424.         }
  425.     }
  426.     if(!(in_buffer=(UC *)malloc(0xFFFF)))
  427.     {
  428.           printf("Could not allocate input 64K memory buffer!\n");
  429.           exit(1);
  430.     }
  431.     else
  432.     {
  433.           memset(in_buffer,0,0xFFFF);
  434.     }
  435.     if(!(out_buffer=(UC *)malloc(0xFFFF)))
  436.     {
  437.           printf("Could not allocate output 64K memory buffer!\n");
  438.           exit(1);
  439.     }
  440.     else
  441.     {
  442.           memset(out_buffer,0,0xFFFF);
  443.     }
  444.     strcpy(temp_str,input_name);
  445.     strcpy(temp_str2,input_name);
  446.     strcat(temp_str,".SLT");
  447.     strcat(temp_str2,".slt");
  448.     if(!(input_handle = fopen(temp_str,"rb")))
  449.     {
  450.         if(!(input_handle = fopen(temp_str2,"rb")))
  451.         {
  452.             perror("Error:");
  453.             printf("\nCould not open input file %s.\n",temp_str);
  454.             printf("Or %s\n",temp_str2);
  455.             free(in_buffer);
  456.             free(out_buffer);
  457.             exit(1);
  458.         }
  459.     }
  460.     fseek(input_handle,0,SEEK_END); /* Something is not quite right */
  461.     temp_long=ftell(input_handle);  /* With feof() */
  462.     fseek(input_handle,0,SEEK_SET);
  463.  
  464.     process_and_copy_z80();
  465.     fread(in_buffer,1,6,input_handle); /* Skip ID_000 & ID_String */
  466.     process_table(temp_long);
  467.     for(x=0;x<256;x++)
  468.     {
  469.         write_DAT(x);
  470.     }
  471.     /* write instructions */
  472.     write_SCR();
  473.     /* write scanned pictures !!! */
  474.     /* write pokes */
  475.     fclose(input_handle);
  476.     free(in_buffer);
  477.     free(out_buffer);
  478. }